﻿using System;
using System.Linq;
using FluentValidation;
using LINQPad.OpenAccess.Services;
using LINQPad.OpenAccess.UI.Services;
using LINQPad.OpenAccess.UI.ViewModel;
using LINQPad.OpenAccess.UI.ViewModel.Validators;
using Ninject.Modules;

namespace LINQPad.OpenAccess.UI.Configuration
{
    /// <summary>
    /// <see cref="NinjectModule"/> for the current assembly.
    /// </summary>
    public class LINQPadOpenAccessUIModule : NinjectModule
    {
        #region Private

        #region - Functions

        /// <summary>
        /// Binds the view models and validators.
        /// </summary>
        private void BindViewModelsAndValidators( )
        {
            this.Bind<IConnectionSettingsViewModel>( ).To<PredefinedConnectionSettingsViewModel>( );
            this.Bind<IConnectionSettingsViewModel>( ).To<CustomConnectionSettingsViewModel>( );
            this.Bind<IConnectionSettingsViewModel>( ).To<MsSqlConnectionSettingsViewModel>( );

            this.Bind<IValidator<DriverSettingsViewModel>>( ).To<DriverSettingsViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<BackendSettingsViewModel>>( ).To<BackendSettingsViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<BasicSettingsViewModel>>( ).To<BasicSettingsViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<ConnectionSettingsHostViewModel>>( ).To<ConnectionSettingsHostViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<CustomConnectionSettingsViewModel>>( ).To<CustomConnectionSettingsViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<PredefinedConnectionSettingsViewModel>>( ).To<PredefinedConnectionSettingsViewModelValidator>( ).InSingletonScope( );
            this.Bind<IValidator<MsSqlConnectionSettingsViewModel>>( ).To<MsSqlConnectionSettingsViewModelValidator>( ).InSingletonScope( );
        }

        #endregion

        #endregion

        #region NinjectModule members

        /// <summary>
        /// Loads the module into the kernel.
        /// </summary>
        public override void Load( )
        {
            this.Rebind<IDataContextUserInteractionService>( ).To<DataContextUserInteractionService>( ).InSingletonScope( );
            this.Bind<IUserInteractionService>( ).To<UserInteractionService>( ).InSingletonScope( );
            this.Bind<IValidatorFactory>( ).To<ServiceLocatorBasedValidatorFactory>( ).InSingletonScope( );
            this.Bind<IConnectionSettingsViewFactory>( ).To<ConnectionSettingsViewFactory>( ).InSingletonScope( );

            this.BindViewModelsAndValidators( );
        }

        #endregion
    }
}
